package com.gengzp.gateway.service.impl;

import com.gengzp.gateway.service.GatewayService;
import com.gengzp.gateway.utils.HttpRequestUtils;
import com.gengzp.rpc.utils.RpcUtils;
import jakarta.servlet.http.HttpServletRequest;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;

import java.io.BufferedReader;
import java.util.LinkedHashMap;
import java.util.Map;

import static com.gengzp.gateway.constants.UrlConstants.GATEWAY_URL_PATH;
import static com.gengzp.gateway.constants.UrlConstants.HTTP_PROTOCOL;

/**
 * @ClassName GatewayServiceImpl
 * @Description 网关服务层实现
 * @Author gengzp
 * @Date 2025/9/23 15:55
 */
@Service
public class GatewayServiceImpl implements GatewayService {

    @Override
    public Object doExecute(HttpServletRequest request, String traceId) {
        // 去掉请求url中网关的部分
        String requestUrl = request.getRequestURI().replace(GATEWAY_URL_PATH, "");
        String[] requestUrlSplit = requestUrl.split("/");

        // 服务地址
        String serviceAddress = null;
        try {
            serviceAddress = RpcUtils.getAddressByServiceName(requestUrlSplit[0]);
        } catch (Exception ignored) {
        }
        if (StringUtils.isBlank(serviceAddress)) {
            return buildFailResult(503, "网关路由失败, 未找到在线服务实例", traceId);
        }

        // 将远程服务调用url截取出实际ip和端口号的部分
        String url = HTTP_PROTOCOL + serviceAddress.split("/")[0] + requestUrl.replace(requestUrlSplit[0], "");

        // 组装请求头
        Map<String, String> headers = new LinkedHashMap<>();
        headers.put("Authorization", request.getHeader("Authorization"));
        headers.put("traceId", traceId);
        headers.put("Content-Type", "application/json");

        // 从输入流中读取请求体
        String requestBody = null;
        try {
            BufferedReader reader = request.getReader();
            StringBuilder bodyBuilder = new StringBuilder();
            String lint;
            while ((lint = reader.readLine()) != null) {
                bodyBuilder.append(lint);
            }
            requestBody = bodyBuilder.toString();
        } catch (Exception e) {
            return buildFailResult(500, "参数信息读取失败" + e.getMessage(), traceId);
        }

        Object result = null;
        try {
            result = HttpRequestUtils.post(url, requestBody, headers);
        } catch (Exception e) {
            return buildFailResult(500, e.getMessage(), traceId);
        }

        return result;
    }

    private Map<String, Object> buildFailResult(int code, String message, String traceId) {
        Map<String, Object> result = new LinkedHashMap<>();
        result.put("code", code);
        result.put("message", message);
        result.put("data", null);
        result.put("traceId", traceId);
        return result;
    }

}
